/**
 * **************** Copyright (C) *****************
 * <p/>
 * Version       Date            Author
 * ─────────────────────────────────────
 * V1.0        2017/7/3         yellowlgx
 * <p/>
 * **************** End of Head *******************
 */
package com.skyworth.ui.newrecycleview;

import android.content.Context;
import android.os.SystemClock;
import android.support.v7.widget.NewRecycleAdapter;
import android.support.v7.widget.NewRecyclerView;
import android.support.v7.widget.OrientationHelper;
import android.support.v7.widget.RecyclerView;
import android.view.KeyEvent;
import android.view.View;
import android.widget.FrameLayout;

import com.skyworth.commen.ui.R;
import com.skyworth.util.SystemUtil;

import java.util.List;

/**
 * @author : yellowlgx
 * @ClassName NewRecycleLayout
 * @Description : TODO
 * @date : 2017/7/3 14:33
 */
public class NewRecycleLayout<T> extends FrameLayout implements OnItemFocusChangeListener, OnItemClickListener, OnBoundaryListener, OnScrollStateListener, OnLoadMoreListener {
    private static final String TAG = "NewRecycleLayout";

    private int DROP_KEY_TIME = 200;

    private OnItemFocusChangeListener mItemFocusChangeListener = null;
    private OnItemClickListener mItemClickListener = null;
    private OnBoundaryListener mBoundaryListener = null;
    private OnScrollStateListener mScrollStateListener = null;
    private OnLoadMoreListener mLoadMoreListener = null;
    private OnScrollBarOnKeyListener mScrollBarListener = null;

    protected NewRecycleAdapter<T> mAdapter;
    protected NewRecyclerView mRecyclerView;
    protected NewLayoutManager mLayoutManager;
    private List<T> itemDatas;

    private NewVerticalScrollBar mScrollBar;

    private int mChildHeight = 0;

    protected int mVSpace = 0, mHSpace = 0;

    private long lastOnKeyTime = 0;

    private int mSpanCount = 1;

    protected boolean move = false;

    protected boolean isSmoothScroll = false;

    protected int scrollToPosition = 0;

    protected boolean middleScroll = false;

    protected FrameLayout.LayoutParams recycleParams;
    private int scrollOffset = 0;
    private int targetScrollPosition = 0;

    public void setmItemFocusChangeListener(OnItemFocusChangeListener listener) {
        mItemFocusChangeListener = listener;
    }

    public void setmItemClickListener(OnItemClickListener listener) {
        mItemClickListener = listener;
    }

    public void setmBoundaryListener(OnBoundaryListener listener) {
        mBoundaryListener = listener;
    }

    public void setmScrollStateListener(OnScrollStateListener listener) {
        mScrollStateListener = listener;
    }

    public void setmLoadMoreListener(OnLoadMoreListener listener) {
        mLoadMoreListener = listener;
    }

    public void setOnScrollBarOnKeyListener(OnScrollBarOnKeyListener listener) {
        mScrollBarListener = listener;
    }

    public void setItemSpace(int hSpace, int vSpace) {
        mHSpace = hSpace;
        mVSpace = vSpace;
//        mLayoutManager.setScorllOfset(hSpace, vSpace);
        mRecyclerView.addItemDecoration(new SpaceItemDecoration(hSpace, vSpace));
    }

    public NewRecycleLayout(Context context) {
        super(context);
        mSpanCount = 1;
        init(1);
    }

    public NewRecycleLayout(Context context, int spanCount) {
        super(context);
        mSpanCount = spanCount;
        init(spanCount);
    }

    public NewRecycleLayout(Context context, int spanCount, int orientation) {
        this(context, spanCount);
        mLayoutManager.setOrientation(orientation);
    }

    @Override
    public boolean post(Runnable action) {
        if(mRecyclerView != null)
            return mRecyclerView.post(action);
        return super.post(action);
    }

    @Override
    public boolean postDelayed(Runnable action, long delayMillis) {
        if(mRecyclerView != null)
            return mRecyclerView.postDelayed(action, delayMillis);
        return super.postDelayed(action, delayMillis);
    }

    public void setOrientation(int orientation) {
        mLayoutManager.setOrientation(orientation);
    }

    public void setSpanCount(int spanCount) {
        mSpanCount = spanCount;
        mRecyclerView.setSpanCount(spanCount);
        mLayoutManager.setSpanCount(spanCount);
    }

    public int getSpanCount() {
        return mSpanCount;
    }

    public void setScrollOfset(int offset) {
        setScrollOffset(0, offset);
    }

    public void setScrollOffset(int upOrLeftOffset, int downOrRightOffset) {
        mLayoutManager.setScorllOfset(upOrLeftOffset, downOrRightOffset);
    }

    //此方法用于重写此类的地方重新传入recycleView,慎用
    protected NewRecyclerView getRecyclerView() {
        return new NewRecyclerView(getContext());
    }

    protected void init(int spanCount) {
        /*if (SystemUtil.isHighPerformance()) {
            DROP_KEY_TIME = 110;
            if (spanCount == 1)
                DROP_KEY_TIME = 70;
        } else {
            DROP_KEY_TIME = 140;
            if (spanCount == 1)
                DROP_KEY_TIME = 90;
        }*/
        mRecyclerView = getRecyclerView();
        mRecyclerView.setOnScrolledListener(this);
        mRecyclerView.setSpanCount(spanCount);
        recycleParams = new FrameLayout.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
        this.addView(mRecyclerView, recycleParams);
        mLayoutManager = new NewLayoutManager(getContext(), spanCount);
        mRecyclerView.setLayoutManager(mLayoutManager);
    }

    public void setLayoutManager(NewLayoutManager layoutManager) {
        mLayoutManager = layoutManager;
        mRecyclerView.setLayoutManager(mLayoutManager);
    }

    @Override
    public void setClipChildren(boolean clipChildren) {
        super.setClipChildren(clipChildren);
        mRecyclerView.setClipChildren(clipChildren);
    }

    @Override
    public void setClipToPadding(boolean clipToPadding) {
        super.setClipToPadding(clipToPadding);
        mRecyclerView.setClipToPadding(clipToPadding);
    }

    public void setNewVerticalScrollBar(NewVerticalScrollBar scrollBar) {
        if (scrollBar == null)
            return;

        mScrollBar = scrollBar;
        resetScrollBar();
        mScrollBar.getScrollBarView().setOnKeyListener(new OnKeyListener() {
            @Override
            public boolean onKey(View v, int keyCode, KeyEvent event) {
                int tarPostion = 0;
                if (event.getAction() == KeyEvent.ACTION_DOWN) {
                    if (mScrollBarListener != null)
                        mScrollBarListener.onScrollBarOnKey(v, keyCode);
                    switch (keyCode) {
                        case KeyEvent.KEYCODE_DPAD_UP:
                            tarPostion = mLayoutManager.findFirstVisibleItemPosition() - mSpanCount * 2;
                            if (tarPostion < 0)
                                tarPostion = 0;
                            mRecyclerView.smoothScrollToPosition(tarPostion);
                            setScrollBarPosition(tarPostion, false);
                            return true;

                        case KeyEvent.KEYCODE_DPAD_DOWN:
                            tarPostion = mLayoutManager.findLastVisibleItemPosition() + mSpanCount * 2;
                            if (tarPostion > mAdapter.getItemCount() - 1)
                                tarPostion = mAdapter.getItemCount() - 1;
                            mRecyclerView.smoothScrollToPosition(tarPostion);
                            setScrollBarPosition(tarPostion, false);
                            return true;

                        case KeyEvent.KEYCODE_DPAD_LEFT:
                            mScrollBar.setScrollBarIcon(R.drawable.ic_custom_scrollbar_unfocus_icon);
                            return false;
                        case KeyEvent.KEYCODE_DPAD_RIGHT:
                            return true;
                    }
                }
                return false;
            }
        });
    }

    public void dropKeyOneTime() {
        mRecyclerView.dropKeyOneTime();
    }

    @Override
    public boolean dispatchKeyEvent(KeyEvent event) {
        if (event.getAction() == KeyEvent.ACTION_DOWN) {
            if (event.getKeyCode() == KeyEvent.KEYCODE_DPAD_UP || event.getKeyCode() == KeyEvent.KEYCODE_DPAD_DOWN || event.getKeyCode() == KeyEvent.KEYCODE_DPAD_LEFT || event.getKeyCode() == KeyEvent.KEYCODE_DPAD_RIGHT) {
                long curTime = SystemClock.uptimeMillis();
                if ((curTime - lastOnKeyTime) < DROP_KEY_TIME) {
                    return true;
                }
                lastOnKeyTime = curTime;
            }
        }
        return super.dispatchKeyEvent(event);
    }

    public void setmChildHeight(int childHeight) {
        mChildHeight = childHeight;
    }

    public void setRecyclerAdapter(NewRecycleAdapter<T> adapter) {
        if (adapter == null)
            return;

        mAdapter = adapter;
        mAdapter.setOnBoundaryListener(this);
        mAdapter.setOnItemClickListener(this);
        mAdapter.setOnItemFocusChangeListener(this);
        mAdapter.setOnLoadMoreListener(this);
        mRecyclerView.setAdapter(mAdapter);
        resetScrollBar();
    }

    public NewRecycleAdapter<T> getRecyclerAdapter() {
        return mAdapter;
    }

    private void resetScrollBar() {
        if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL && mScrollBar != null) {
            mRecyclerView.post(new Runnable() {
                @Override
                public void run() {
                    int temp = mRecyclerView.getHeight() / mChildHeight;

                    int gridTotalHeight = mRecyclerView.getRow(mAdapter.getItemCount() - 1) * mChildHeight - (temp * mChildHeight);
                    setScrollBarPosition(0, true);
                    if (gridTotalHeight > 0) {
                        if (mScrollBar.getVisibility() != View.VISIBLE)
                            mScrollBar.setVisibility(View.VISIBLE);
                    } else if (gridTotalHeight <= 0) {
                        if (mScrollBar.getVisibility() == View.VISIBLE)
                            mScrollBar.setVisibility(View.GONE);
                    }
                }
            });
        }
    }

    public void setSelection(final int position) {
        scrollToPosition(position);

        mRecyclerView.post(new Runnable() {
            @Override
            public void run() {
                final View view = mLayoutManager.findViewByPosition(position);
                if (view != null && !view.hasFocus()) {
                    view.post(new Runnable() {
                        @Override
                        public void run() {
                            view.requestFocus();
                        }
                    });
                    return;
                }

                mRecyclerView.postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        scrollToPosition(position);
                        if(NewRecycleLayout.this.getVisibility() != View.VISIBLE)
                            return;
                        final View view = mLayoutManager.findViewByPosition(position);
                        if (view != null && !view.hasFocus()) {
                            view.post(new Runnable() {
                                @Override
                                public void run() {
                                    view.requestFocus();
                                }
                            });
                        }
                    }
                }, 250);
            }
        });
    }

    public void onDestroy() {
        final int firstPosition = mLayoutManager.findFirstVisibleItemPosition();
        final int lastPosition = mLayoutManager.findLastVisibleItemPosition();
        for (int i = firstPosition; i <= lastPosition; i++) {
            NewRecycleViewHolder holder = (NewRecycleViewHolder) mRecyclerView.findViewHolderForAdapterPosition(i);
            if (holder != null) {
                holder.destroy();
            }
        }
        mRecyclerView.setOnScrolledListener(null);
    }

    public int getChildItemCount() {
        return mLayoutManager != null ? mLayoutManager.getChildCount() : 0;
    }

    public int getItemPosition(View item) {
        return mRecyclerView.getChildLayoutPosition(item);
    }

    public View getItemByPosition(int position) {
        return mLayoutManager.findViewByPosition(position);
    }

    public void notifyDataSetChanged() {
        if(mAdapter == null) {
            return;
        }
        mRecyclerView.reset();

        mAdapter.notifyDataSetChanged();
        mRecyclerView.postDelayed(new Runnable() {
            @Override
            public void run() {
                int firstPosition = mLayoutManager.findFirstVisibleItemPosition();
                int lastPosition = mLayoutManager.findLastVisibleItemPosition();
                if (mRecyclerView.getScrollState() == RecyclerView.SCROLL_STATE_IDLE) {
                    //                    Log.v("lgx", "notifyDataSetChanged firstPosition--> " + firstPosition + "  " +
                    //                            "lastPosition--> " + lastPosition);
                    for (int i = firstPosition; i <= lastPosition; i++) {
                        NewRecycleViewHolder holder = (NewRecycleViewHolder) mRecyclerView.findViewHolderForAdapterPosition(i);
                        if (holder != null) {
                            holder.refreshUI();
                        }
                    }
                }
            }
        }, 200);
    }

    public void notifyItemChanged(int position) {
        if(mAdapter == null) {
            return;
        }

        mAdapter.notifyItemChanged(position);
        NewRecycleViewHolder holder = (NewRecycleViewHolder) mRecyclerView.findViewHolderForAdapterPosition(position);
        if (holder != null) {
            holder.setData(mAdapter.getItem(position), position);
            holder.refreshUI();
        }
    }

    public void notifyItemRangeChanged(final int positionStart, int itemCount) {
        if (mAdapter != null) {
            mAdapter.notifyItemRangeInserted(positionStart, itemCount);
        }
        //        final int firstPosition = mLayoutManager.findFirstVisibleItemPosition();
        //        final int lastPosition = mLayoutManager.findLastVisibleItemPosition();
        //
        //        final View focuseView = mRecyclerView.getFocusedChild();
        //        final int focusePosition = focuseView!= null ? mLayoutManager.getPosition(focuseView) :
        // lastPosition;
        //
        //        if (mAdapter != null)
        //        {
        //            Log.v("lgx", "notifyItemRangeChanged focusePosition---> " + focusePosition);
        //            mTempFocusView.requestFocus();
        //            mAdapter.notifyItemRangeChanged(firstPosition, itemCount);
        //
        //            mRecyclerView.postDelayed(new Runnable()
        //            {
        //                @Override
        //                public void run()
        //                {
        //                    Log.v("lgx", "-----------post------------" + mRecyclerView.getScrollState());
        //                    if (mRecyclerView.getScrollState() == RecyclerView.SCROLL_STATE_IDLE)
        //                    {
        //                        for (int i = firstPosition; i <= lastPosition; i++)
        //                        {
        //                            NewRecycleViewHolder holder =
        //                                    (NewRecycleViewHolder) mRecyclerView.findViewHolderForAdapterPosition
        // (i);
        //                            if (holder != null)
        //                            {
        //                                holder.refreshUI();
        //                                if (holder.getmPosition() == focusePosition && !holder.itemView.hasFocus())
        //                                {
        //                                    Log.v("lgx", "post holder.getmPosition()---> " + holder.getmPosition());
        //                                    holder.itemView.requestFocus();
        //                                }
        //                            }
        //                        }
        //                    }
        //                }
        //            }, 600);
        //        }
    }

    public void notifyItemInserted(int position) {
        if (mAdapter != null)
            mAdapter.notifyItemInserted(position);
    }

    public void notifyItemMoved(int fromPosition, int toPosition) {
        if (mAdapter != null)
            mAdapter.notifyItemMoved(fromPosition, toPosition);
    }

    public void notifyItemRemoved(final int position) {
        if(mAdapter == null) {
            return;
        }
        mAdapter.notifyItemRemoved(position);
        mRecyclerView.postDelayed(new Runnable() {
            @Override
            public void run() {
                int last = mLayoutManager.findLastVisibleItemPosition();
                for (int i = position; i <= last; i++) {
                    NewRecycleViewHolder holder = (NewRecycleViewHolder) mRecyclerView.findViewHolderForAdapterPosition(i);
                    if (holder != null) {
                        holder.refreshUI();
                    }
                }
            }
        }, 300);
    }

    public void notifyItemRangeInserted(final int positionStart, int itemCount) {
        if (mAdapter != null) {
            mRecyclerView.reset();
            mAdapter.notifyItemRangeInserted(positionStart, itemCount);
            //            mRecyclerView.post(new Runnable()
            //            {
            //                @Override
            //                public void run()
            //                {
            //                    if (mRecyclerView.getScrollState() == RecyclerView.SCROLL_STATE_IDLE)
            //                    {
            //                        int last = mLayoutManager.findLastVisibleItemPosition();
            //                        for (int i = positionStart; i <= last; i++)
            //                        {
            //                            NewRecycleViewHolder holder =
            //                                    (NewRecycleViewHolder) mRecyclerView.findViewHolderForAdapterPosition
            // (i);
            //                            if (holder != null)
            //                            {
            //                                holder.refreshUI();
            //                            }
            //                        }
            //                    }
            //                }
            //            });
        }
    }

    public void notifyItemRangeRemoved(int positionStart, int itemCount) {
        if (mAdapter != null)
            mAdapter.notifyItemRangeRemoved(positionStart, itemCount);
    }


    public int getFirstVisiblePosition() {
        return mLayoutManager.findFirstVisibleItemPosition();
    }

    public int getLastVisiblePosition() {
        return mLayoutManager.findLastVisibleItemPosition();
    }

    public View getViewByPosition(int position) {
        return mLayoutManager.findViewByPosition(position);
    }

    public void smoothScrollBy(int dx, int dy) {
        mRecyclerView.smoothScrollBy(dx, dy);
    }

    public void scrollBy(int dx, int dy) {
        mRecyclerView.scrollBy(dx, dy);
    }

    /**
     * @Description 带滚动效果的滚动到指定位置
     */
    public void smoothScrollToPosition(final int position) {
        if(mAdapter == null) {
            return;
        }
        if (position < 0 || position >= mAdapter.getItemCount()) {
            return;
        }

        mRecyclerView.reset();
        int firstItem = getFirstVisiblePosition();
        int lastItem = getLastVisiblePosition();
        targetScrollPosition = position;
        scrollOffset = 0;
        if (position < firstItem) {
            if(mLoadMoreListener != null)
                mLoadMoreListener.onLoadPre(getViewByPosition(firstItem), firstItem, firstItem);
        } else if (position > lastItem) {
            if(mLoadMoreListener != null)
                mLoadMoreListener.onLoadMore(getViewByPosition(lastItem), getLastVisiblePosition(), mAdapter.getItemCount());
        }
        if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
            int curFirstRow = getRow(firstItem);
            int curLastRow = getRow(lastItem);
            int screenTotalRow = curLastRow - curFirstRow + 1;
            if (position < firstItem) {
                if(middleScroll) {
                    targetScrollPosition -= ((screenTotalRow - 1) / 2) * mSpanCount;
                } else {
//                    targetPosition -= (screenTotalRow - 1) * mSpanCount;
                }
                if(targetScrollPosition < 0) {
                    targetScrollPosition = 0;
                }
            } else if (position > lastItem) {
                if(middleScroll) {
                    targetScrollPosition += ((screenTotalRow - 1) / 2) * mSpanCount;
                } else {
                    targetScrollPosition += (screenTotalRow - 1)  * mSpanCount;
                    if(getViewByPosition(firstItem) != null)
                        scrollOffset = screenTotalRow * (getViewByPosition(firstItem).getWidth() + mHSpace) - this.getWidth();
                }
                if(targetScrollPosition >= mAdapter.getItemCount()) {
                    targetScrollPosition = mAdapter.getItemCount() - 1;
                }
            }else {
//                if(middleScroll) {
//                    targetScrollPosition += ((screenTotalRow - 1) / 2) * mSpanCount;
//                } else {
//                    targetScrollPosition += (screenTotalRow - 1)  * mSpanCount;
//                    if(getViewByPosition(firstItem) != null)
//                        scrollOffset = screenTotalRow * (getViewByPosition(firstItem).getWidth() + mHSpace) - this.getWidth();
//                }
//                if(targetScrollPosition >= mAdapter.getItemCount()) {
//                    targetScrollPosition = mAdapter.getItemCount() - 1;
//                }
            }
        } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
            int curFirstCol = getCol(firstItem);
            int curLastCor = getCol(lastItem);
            int screenTotalCol = curLastCor - curFirstCol + 1;
            if (position < firstItem) {
                if(middleScroll) {
                    targetScrollPosition -= ((screenTotalCol - 1) / 2) * mSpanCount;
                } else {
//                    targetPosition -= (screenTotalCol - 1) * mSpanCount;
                }
                if(targetScrollPosition < 0) {
                    targetScrollPosition = 0;
                }
            } else if (position > lastItem) {
                if(middleScroll) {
                    targetScrollPosition += ((screenTotalCol - 1) / 2) * mSpanCount;
                } else {
                    targetScrollPosition += (screenTotalCol - 1) * mSpanCount;
                    if(getViewByPosition(firstItem) != null)
                        scrollOffset = screenTotalCol * (getViewByPosition(firstItem).getHeight() + mVSpace) - this.getHeight();
                }
                if(targetScrollPosition >= mAdapter.getItemCount()) {
                    targetScrollPosition = mAdapter.getItemCount() - 1;
                }
            } else {
//                if(middleScroll) {
//                    targetScrollPosition += ((screenTotalCol - 1) / 2) * mSpanCount;
//                } else {
//                    targetScrollPosition += (screenTotalCol - 1) * mSpanCount;
//                    if(getViewByPosition(firstItem) != null)
//                        scrollOffset = screenTotalCol * (getViewByPosition(firstItem).getHeight() + mVSpace) - this.getHeight();
//                }
//                if(targetScrollPosition >= mAdapter.getItemCount()) {
//                    targetScrollPosition = mAdapter.getItemCount() - 1;
//                }
            }
        }
        if(scrollOffset != 0 && (position < firstItem || position > lastItem)) {
            mRecyclerView.addOnScrollListener(scrollListener);
            if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
                recycleParams.width = this.getWidth() + scrollOffset;
            } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
                recycleParams.height = this.getHeight() + scrollOffset;
            }
            mRecyclerView.setLayoutParams(recycleParams);
        }
        scrollOffset = 0;
        mRecyclerView.post(new Runnable() {
            @Override
            public void run() {
                mRecyclerView.smoothScrollToPosition(targetScrollPosition);
            }
        });
        scrollToPositionEvent(targetScrollPosition, false);

//        scrollToPosition = position;
//        isSmoothScroll = true;
//        //        mRecyclerView.smoothScrollToPosition(position);
//        int firstItem = mLayoutManager.findFirstVisibleItemPosition();
//        int lastItem = mLayoutManager.findLastVisibleItemPosition();
//        if (position <= firstItem) {
//            mRecyclerView.smoothScrollToPosition(position);
//            move = true;
//        } else if (position <= lastItem) {
//            if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
//                int left = mRecyclerView.getChildAt(position - firstItem).getLeft();
//                if (left > 0) {
//                    left -= middleScroll ? mHSpace / 2 : mHSpace;
//                    if(middleScroll) {
//                        left -= (getWidth() / 2 - mRecyclerView.getChildAt(position - firstItem).getWidth() / 2);
//                    }
//                } else {
//                    left += middleScroll ? mHSpace / 2 : mHSpace;
//                    if(middleScroll) {
//                        left += (getWidth() / 2 - mRecyclerView.getChildAt(position - firstItem).getWidth() / 2);
//                    }
//                }
//                mRecyclerView.smoothScrollBy(left, 0);
//            } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
//                int top = mRecyclerView.getChildAt(position - firstItem).getTop();
//                if (top > 0) {
//                    top -= middleScroll ? mVSpace / 2 : mVSpace;
//                    if(middleScroll) {
//                        top -= (getHeight() / 2 - mRecyclerView.getChildAt(position - firstItem).getHeight() / 2);
//                    }
//                } else {
//                    top += middleScroll ? mVSpace / 2 : mVSpace;
//                    if(middleScroll) {
//                        top += (getHeight() / 2 - mRecyclerView.getChildAt(position - firstItem).getHeight() / 2);
//                    }
//                }
//                mRecyclerView.smoothScrollBy(0, top);
//            }
//        } else {
//            mRecyclerView.smoothScrollToPosition(position);
//            move = true;
//        }
//        scrollToPositionEvent(position);
    }

    RecyclerView.OnScrollListener scrollListener = new RecyclerView.OnScrollListener() {
        @Override
        public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
            super.onScrollStateChanged(recyclerView, newState);
            if(newState == RecyclerView.SCROLL_STATE_IDLE) {
                boolean need = false;
                if (recycleParams.width != LayoutParams.MATCH_PARENT
                        && mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
                    if(mRecyclerView.getWidth() != NewRecycleLayout.this.getWidth()) {
                        recycleParams.width = NewRecycleLayout.this.getWidth();
                        need = true;
                    }
                } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
                    if(recycleParams.height != LayoutParams.MATCH_PARENT
                            && mRecyclerView.getHeight() != NewRecycleLayout.this.getHeight()) {
                        recycleParams.height = NewRecycleLayout.this.getHeight();
                        need = true;
                    }
                }
                if(need) {
                    mRecyclerView.post(new Runnable() {
                        @Override
                        public void run() {
                            mRecyclerView.setLayoutParams(recycleParams);
                        }
                    });
                }
                mRecyclerView.removeOnScrollListener(scrollListener);
            }
        }
    };

    /**
     * @Description 直接移动到指定位置
     */
    public void scrollToPosition(int position) {
        if(mAdapter == null) {
            return;
        }

        if (position < 0 || position >= mAdapter.getItemCount()) {
            return;
        }

        mRecyclerView.reset();
        int firstItem = getFirstVisiblePosition();
        int lastItem = getLastVisiblePosition();
        targetScrollPosition = position;
        scrollOffset = 0;
        if (position < firstItem) {
            if(mLoadMoreListener != null)
                mLoadMoreListener.onLoadPre(getViewByPosition(firstItem), firstItem, firstItem);
        } else if (position > lastItem) {
            if(mLoadMoreListener != null)
                mLoadMoreListener.onLoadMore(getViewByPosition(lastItem), getLastVisiblePosition(), mAdapter.getItemCount());
        }
        if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
            int curFirstRow = getRow(firstItem);
            int curLastRow = getRow(lastItem);
            int screenTotalRow = curLastRow - curFirstRow + 1;
            if (position < firstItem) {
                if(middleScroll) {
                    targetScrollPosition -= ((screenTotalRow - 1) / 2) * mSpanCount;
                } else {
                    //                    targetPosition -= (screenTotalRow - 1) * mSpanCount;
                }
                if(targetScrollPosition < 0) {
                    targetScrollPosition = 0;
                }
            } else if (position > lastItem) {
                if(middleScroll) {
                    targetScrollPosition += ((screenTotalRow - 1) / 2) * mSpanCount;
                } else {
                    targetScrollPosition += (screenTotalRow - 1)  * mSpanCount;
                    if(getViewByPosition(firstItem) != null)
                        scrollOffset = screenTotalRow * (getViewByPosition(firstItem).getWidth() + mHSpace) - this.getWidth();
                }
                if(targetScrollPosition >= mAdapter.getItemCount()) {
                    targetScrollPosition = mAdapter.getItemCount() - 1;
                }
            } else {
//                if(middleScroll) {
//                    targetScrollPosition += ((screenTotalRow - 1) / 2) * mSpanCount;
//                } else {
//                    targetScrollPosition += (screenTotalRow - 1)  * mSpanCount;
//                    if(getViewByPosition(firstItem) != null)
//                        scrollOffset = screenTotalRow * (getViewByPosition(firstItem).getWidth() + mHSpace) - this.getWidth();
//                }
//                if(targetScrollPosition >= mAdapter.getItemCount()) {
//                    targetScrollPosition = mAdapter.getItemCount() - 1;
//                }
            }
        } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
            int curFirstCol = getCol(firstItem);
            int curLastCor = getCol(lastItem);
            int screenTotalCol = curLastCor - curFirstCol + 1;
            if (position < firstItem) {
                if(middleScroll) {
                    targetScrollPosition -= ((screenTotalCol - 1) / 2) * mSpanCount;
                } else {
                    //                    targetPosition -= (screenTotalCol - 1) * mSpanCount;
                }
                if(targetScrollPosition < 0) {
                    targetScrollPosition = 0;
                }
            } else if (position > lastItem) {
                if(middleScroll) {
                    targetScrollPosition += ((screenTotalCol - 1) / 2) * mSpanCount;
                } else {
                    targetScrollPosition += (screenTotalCol - 1) * mSpanCount;
                    if(getViewByPosition(firstItem) != null)
                        scrollOffset = screenTotalCol * (getViewByPosition(firstItem).getHeight() + mVSpace) - this.getHeight();
                }
                if(targetScrollPosition >= mAdapter.getItemCount()) {
                    targetScrollPosition = mAdapter.getItemCount() - 1;
                }
            } else {
//                if(middleScroll) {
//                    targetScrollPosition += ((screenTotalCol - 1) / 2) * mSpanCount;
//                } else {
//                    targetScrollPosition += (screenTotalCol - 1) * mSpanCount;
//                    if(getViewByPosition(firstItem) != null)
//                        scrollOffset = screenTotalCol * (getViewByPosition(firstItem).getHeight() + mVSpace) - this.getHeight();
//                }
//                if(targetScrollPosition >= mAdapter.getItemCount()) {
//                    targetScrollPosition = mAdapter.getItemCount() - 1;
//                }
            }
        }
        if(scrollOffset != 0 && (position < firstItem || position > lastItem)) {
            mRecyclerView.addOnScrollListener(scrollListener);
            if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
                recycleParams.width = this.getWidth() + scrollOffset;
            } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
                recycleParams.height = this.getHeight() + scrollOffset;
            }
            mRecyclerView.setLayoutParams(recycleParams);
        }
        scrollOffset = 0;
        mRecyclerView.post(new Runnable() {
            @Override
            public void run() {
                mRecyclerView.scrollToPosition(targetScrollPosition);
            }
        });
        boolean need = false;
        if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
            if(recycleParams.width != LayoutParams.MATCH_PARENT
                    && recycleParams.width != NewRecycleLayout.this.getWidth()) {
                recycleParams.width = NewRecycleLayout.this.getWidth();
                need = true;
            }
        } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
            if(recycleParams.height != LayoutParams.MATCH_PARENT
                    && recycleParams.height != NewRecycleLayout.this.getHeight()) {
                recycleParams.height = NewRecycleLayout.this.getHeight();
                need = true;
            }
        }
        if(need) {
            mRecyclerView.post(new Runnable() {
                @Override
                public void run() {
                    mRecyclerView.setLayoutParams(recycleParams);
                }
            });
        }
        scrollToPositionEvent(targetScrollPosition, true);

//        scrollToPosition = position;
//        isSmoothScroll = false;
//        int firstItem = mLayoutManager.findFirstVisibleItemPosition();
//        int lastItem = mLayoutManager.findLastVisibleItemPosition();
//        if (position <= firstItem) {
//            mRecyclerView.scrollToPosition(position);
//            move = true;
//        } else if (position <= lastItem) {
//            if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
//                int left = mRecyclerView.getChildAt(position - firstItem).getLeft();
//                if (left > 0) {
//                    left -= middleScroll ? mHSpace / 2 : mHSpace;
//                    if(middleScroll) {
//                        left -= (getWidth() / 2 - mRecyclerView.getChildAt(position - firstItem).getWidth() / 2);
//                    }
//                } else {
//                    left += middleScroll ? mHSpace / 2 : mHSpace;
//                    if(middleScroll) {
//                        left += (getWidth() / 2 - mRecyclerView.getChildAt(position - firstItem).getWidth() / 2);
//                    }
//                }
//                mRecyclerView.scrollBy(left, 0);
//            } else if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
//                int top = mRecyclerView.getChildAt(position - firstItem).getTop();
//                if (top > 0) {
//                    top -= middleScroll? mVSpace / 2 : mVSpace;
//                    if(middleScroll) {
//                        top -= (getHeight() / 2 - mRecyclerView.getChildAt(position - firstItem).getHeight() / 2);
//                    }
//                } else {
//                    top += middleScroll? mVSpace / 2 : mVSpace;
//                    if(middleScroll) {
//                        top += (getHeight() / 2 - mRecyclerView.getChildAt(position - firstItem).getHeight() / 2);
//                    }
//                }
//                Log.v("lgx", " top -- > " + top);
//                mRecyclerView.scrollBy(0, top);
//            }
//        } else {
//            mRecyclerView.scrollToPosition(position);
//            move = true;
//        }
//        scrollToPositionEvent(position);

//        mRecyclerView.scrollToPosition(position);
//        scrollToPositionEvent(position);
    }

    /**
     * @param position
     * @return int
     * @Description 获取当前位置所在列数<br/>
     */
    public int getCol(int position) {
        return mRecyclerView.getCol(position);
    }

    /**
     * @param position
     * @return int
     * @Description 获取当前位置所在行数<br/>
     */
    public int getRow(int position) {
        return mRecyclerView.getRow(position);
    }

    /**
     * @param position
     * @return int
     * @Description 判断当前位置是否是最后一列<br/>
     */
    public boolean isLastCol(int position) {
        return mRecyclerView.isLastRow(position);
    }

    /**
     * @param position
     * @return int
     * @Description 判断当前位置是否是第一列<br/>
     */
    public boolean isFirstCol(int position) {
        return mRecyclerView.isFirstCol(position);
    }

    /**
     * @param position
     * @return int
     * @Description 判断当前位置是否是最后一行<br/>
     */
    public boolean isLastRow(int position) {
        return mRecyclerView.isLastRow(position);
    }

    /**
     * @param position
     * @return int
     * @Description 判断当前位置是否是第一行<br/>
     */
    public boolean isFirstRow(int position) {
        return mRecyclerView.isFirstRow(position);
    }

    protected void scrollToPositionEvent(final int position, final boolean needCallback) {
        mRecyclerView.post(new Runnable() {
            @Override
            public void run() {
                mRecyclerView.refreshCurViewHolder(needCallback);
                setScrollBarPosition(position, false);
            }
        });
    }

    private void setScrollBarPosition(int selectPosition, boolean isFirst) {
        if (mScrollBar != null) {
            int scrollHeight = mScrollBar.getScrollBarHeight() - mScrollBar.getScrollBarViewHeight();

            int totalRow = mRecyclerView.getRow(mAdapter.getItemCount() - 1);
            if (totalRow < 1)
                totalRow = 1;
            //            int totalHeight = (mChildHeight + mVSpace) * totalRow;
            //
            //            int barTotalRow = (totalRow * scrollHeight) / totalHeight;

            int curRow = mRecyclerView.getRow(selectPosition);
            int scrollY = curRow * (scrollHeight / totalRow);
            if (curRow == 1)
                scrollY = 0;
            if (mRecyclerView.isLastRow(selectPosition))
                scrollY = scrollHeight;
            if (isFirst)
                mScrollBar.setFirstScrollBarPosition(scrollY);
            else
                mScrollBar.setScrollBarPosition(scrollY);
        }
    }

    public void setMiddleScroll(boolean middleScroll) {
        this.middleScroll = middleScroll;
        mLayoutManager.setMiddleScroll(middleScroll);
    }

    @Override
    public boolean onLeftBoundary(View leaveView, int position) {
        if (mBoundaryListener != null) {
            // 判断当前位置是否是第一列
            if (mRecyclerView.isFirstCol(position))
                return mBoundaryListener.onLeftBoundary(leaveView, position);
            else {
                if (mBoundaryListener != null)
                    return mBoundaryListener.onOtherKeyEvent(leaveView, position, KeyEvent.KEYCODE_DPAD_LEFT);
            }
        }
        return false;
    }

    @Override
    public boolean onTopBoundary(View leaveView, int position) {
        if (mBoundaryListener != null) {
            //            if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL)
            //            {
            //                return mBoundaryListener.onTopBoundary(leaveView, position);
            //            } else
            //            {
            //                if (position == 0)
            //                    return mBoundaryListener.onTopBoundary(leaveView, position);
            //            }
            // 判断当前位置是否是第一行
            if (mRecyclerView.isFirstRow(position))
                return mBoundaryListener.onTopBoundary(leaveView, position);
            else {
                if (mBoundaryListener != null)
                    return mBoundaryListener.onOtherKeyEvent(leaveView, position, KeyEvent.KEYCODE_DPAD_UP);
            }
        }
        return false;
    }

    @Override
    public boolean onDownBoundary(View leaveView, int position) {
        if (mBoundaryListener != null) {
            //            if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL)
            //            {
            //                return mBoundaryListener.onDownBoundary(leaveView, position);
            //            } else
            //            {
            //                if (position == 0)
            //                    return mBoundaryListener.onDownBoundary(leaveView, position);
            //            }
            // 判断当前位置是否是最后一行
            if (mRecyclerView.isLastRow(position))
                return mBoundaryListener.onDownBoundary(leaveView, position);
            else {
                if (mBoundaryListener != null)
                    return mBoundaryListener.onOtherKeyEvent(leaveView, position, KeyEvent.KEYCODE_DPAD_DOWN);
            }
        }
        return false;
    }

    @Override
    public boolean onRightBoundary(View leaveView, int position) {
        if (mBoundaryListener != null) {
            //            if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL)
            //            {
            //                return mBoundaryListener.onRightBoundary(leaveView, position);
            //            } else
            //            {
            //                if (position == 0)
            //                    return mBoundaryListener.onRightBoundary(leaveView, position);
            //            }
            // 判断当前位置是否是最后一列
            if (mRecyclerView.isLastCol(position)) {
                return mBoundaryListener.onRightBoundary(leaveView, position);
            } else {
                if (mBoundaryListener != null)
                    return mBoundaryListener.onOtherKeyEvent(leaveView, position, KeyEvent.KEYCODE_DPAD_RIGHT);
            }
        }
        return false;
    }

    @Override
    public boolean onOtherKeyEvent(View v, int position, int keyCode) {
        if (mBoundaryListener != null) {
            return mBoundaryListener.onOtherKeyEvent(v, position, keyCode);
        }
        return false;
    }

    @Override
    public void click(View v, int position) {
        if (mItemClickListener != null) {
            mItemClickListener.click(v, position);
        }
    }

    @Override
    public void focusChange(View v, int position, boolean hasFocus) {
        if (mItemFocusChangeListener != null) {
            mItemFocusChangeListener.focusChange(v, position, hasFocus);
        }
    }

    @Override
    public void onScrollby(int selectPosition) {
        setScrollBarPosition(selectPosition, false);
        if (mScrollStateListener != null)
            mScrollStateListener.onScrollby(selectPosition);
    }

    /**
     * @Description 滚动开始时的回调<br/>
     */
    @Override
    public void onScrollStart() {
        if (mScrollStateListener != null)
            mScrollStateListener.onScrollStart();
    }

    /**
     * @param parent       当前ListView
     * @param firstPostion 当前显示中的第一个位置，也就是数据List中的具体位置
     * @param endPosition  当前现显示中的最后一个位置，也就是数据使用到的最后位置 void
     * @Description 滚动结束时的回调<br/>
     */
    @Override
    public void onScrollEnd(NewRecyclerView parent, int firstPostion, int endPosition) {
        if (mScrollStateListener != null)
            mScrollStateListener.onScrollEnd(parent, firstPostion, endPosition);
    }

    @Override
    public void onLoadPre(View view, int curPosition, int firstPosition) {
        if (mLoadMoreListener != null) {
            int firsttVisiblePosition = getFirstVisiblePosition();
            if(firsttVisiblePosition - mSpanCount * 4 > 0) {
                firsttVisiblePosition -= mSpanCount * 4;
            } else {
                firsttVisiblePosition = 0;
            }
            if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
                if (getRow(curPosition) < getRow(getFirstVisiblePosition()) + 4
                        || mAdapter.getItem(firsttVisiblePosition) == null) {
                    mLoadMoreListener.onLoadPre(view, curPosition, getFirstVisiblePosition());
                    //                    dropKeyOneTime();
                }
            } else if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
                if (getCol(curPosition) < getCol(getFirstVisiblePosition()) + 4
                        || mAdapter.getItem(firsttVisiblePosition) == null) {
                    mLoadMoreListener.onLoadPre(view, curPosition, getFirstVisiblePosition());
                    //                    dropKeyOneTime();
                }
            }
        }
    }

    @Override
    public void onLoadMore(View view, int curPosition, int lastPosition) {
        if (mLoadMoreListener != null) {
            int lastVisiblePosition = getLastVisiblePosition();
            if(lastVisiblePosition + mSpanCount * 4 < mAdapter.getItemCount()) {
                lastVisiblePosition += mSpanCount * 4;
            } else {
                lastVisiblePosition = mAdapter.getItemCount() - 1;
            }
            if (mLayoutManager.getOrientation() == OrientationHelper.VERTICAL) {
                if (getRow(curPosition) > getRow(mAdapter.getItemCount() - 1) - 4
                        || mAdapter.getItem(lastVisiblePosition) == null) {
                    mLoadMoreListener.onLoadMore(view, curPosition, lastPosition);
                    dropKeyOneTime();
                }
            } else if (mLayoutManager.getOrientation() == OrientationHelper.HORIZONTAL) {
                if (getCol(curPosition) > getCol(mAdapter.getItemCount() - 1) - 4
                        || mAdapter.getItem(lastVisiblePosition) == null) {
                    mLoadMoreListener.onLoadMore(view, curPosition, lastPosition);
                    dropKeyOneTime();
                }
            }
        }
    }

}
